/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package TorrentEngine;
import Logger.MTLogger;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.OutputStream;

/**
 *
 * @author Dhaval Moliya
 */
public class DirectPeerSender implements PeerSenderInterface{

    OutputStream outputStream;
   

    public int queueControlMessage(byte[] byteArray) throws Exception {
        //throw new UnsupportedOperationException("Not supported yet.");
    	if(outputStream == null)
            return 1;
        try {
              
              outputStream.write(byteArray);
              outputStream.flush();
              //System.out.println("Msg:  " + byteArray);
          } catch (IOException ex) {
               ex.printStackTrace();
               
          }
        return 0;
    }

    public int queueDataMessage(int aPieceIndex, int aBegin, int aLength, MTTorrent torrent, MTPeer peer) throws IOException {
        //throw new UnsupportedOperationException("Not supported yet.");
    	MTPiece piece = torrent.piece(aPieceIndex);

        if(outputStream == null)
            return 1;
        
    	if(piece==null) return 1;
        
    	byte[] block = piece.getBlock(aBegin, aLength);
    	
    	log("Processing piece request " + aPieceIndex + " Begin: " + aBegin + " Length: " + aLength + " while piece totalsize: " + piece.getTotalSize(), peer);

        if(aBegin + aLength > piece.getTotalSize())
        {
            //close("Bad PIECE request (index is out of bounds)");
            return 2;
        }

        if(block == null)
        {
            //close("Failed to extract block of piece");
            return 3;
        } 
    	ByteArrayOutputStream bs = new ByteArrayOutputStream();
        bs.write(putIntToSendBuffer(9 + aLength));
        bs.write(7); //KMessageIdPiece = 7
        bs.write(putIntToSendBuffer(aPieceIndex));
        bs.write(putIntToSendBuffer(aBegin));
        
         bs.write(block);
         bs.flush();
         outputStream.write(bs.toByteArray());
         
         bs.close();
         bs = null;
         return 0;

    }

    public void setOutputStream(OutputStream opStream) throws Exception{
       // throw new UnsupportedOperationException("Not supported yet.");

        outputStream=opStream;
        
    }

    private byte[] putIntToSendBuffer(int aInteger)
    {
        byte[] buffer = new byte[4];

        buffer[3] = (byte) (aInteger & 0xFF);
        buffer[2] = (byte) ((aInteger & (0xFF << 8)) >> 8);
        buffer[1] = (byte) ((aInteger & (0xFF << 16)) >> 16);
        buffer[0] = (byte) ((aInteger & (0xFF << 24)) >> 24);

        return buffer;
    }
    public void log(String aText, MTPeer peer)
    {
        MTLogger.writeLine("[Peer " + peer.getAddress() + ":" + peer.getPort() +
            " " + peer.getClient() + "]");
        MTLogger.writeLine("\t" + aText);
    }
        
}
